/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package desktopapplication;

import static desktopapplication.GlobalVariables.*;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;

import java.util.ArrayList;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.JOptionPane;
import pack.Course;
import pack.Question;
import sun.misc.BASE64Encoder;

/**
 *
 * @author 王舒嶷
 */
public class FunctionLibrary {

    /**
     * this function is called when user logging in
     * it checks whether the entered username and password are matched
     * if matched, then read all the user profile from database
     * @param command
     * @param username
     * @param password
     * @throws IOException 
     */
    public static void sendCommandLogin(String username, String password) throws IOException {
        String command = "LogIn";
        System.out.println("Sending: " + command);
        out.writeObject(command);
        out.writeObject(username);
//        try {
//            password=encoderByMd5(password);
//        } catch (NoSuchAlgorithmException ex) {
//            Logger.getLogger(FunctionLibrary.class.getName()).log(Level.SEVERE, null, ex);
//        } catch (UnsupportedEncodingException ex) {
//            Logger.getLogger(FunctionLibrary.class.getName()).log(Level.SEVERE, null, ex);
//        }
        System.out.println(password);
        out.writeObject(password);
        out.flush();
    }

    /**
     * the function sends command to get the course list from server
     * @param user_id the user id of current user
     * @return the course list corresponding to the user id
     * @throws IOException
     * @throws ClassNotFoundException 
     */
    public static ArrayList<Course> sendCommandGetCourseList(int user_id) throws IOException, ClassNotFoundException {
        String command = "GetCourseList";
        out.writeObject(command);
        out.writeInt(user_id);
        out.flush();
        ArrayList<Course> courseList = new ArrayList<Course>();
        courseList = (ArrayList<Course>) in.readObject();
        return courseList;
    }

    /**
     * 
     * @param user_id
     * @param title
     * @param body
     * @throws IOException 
     */
    public static int sendCommandCreateCourse(int user_id, String title, String body) throws IOException {
        String command = "CreateCourse";
        out.writeObject(command);
        out.writeInt(user_id);
        out.writeObject(title);
        out.writeObject(body);
        out.flush();
        return in.readInt();
    }

    /**
     * 
     * @param course_id
     * @param title
     * @param body
     * @throws IOException 
     */
    public static void sendCommandEditCourse(int course_id, String title, String body) throws IOException {
        String command = "EditCourse";
        out.writeObject(command);
        out.writeInt(course_id);
        out.writeObject(title);
        out.writeObject(body);
        out.flush();
    }

    /**
     * pre:
     * post: sends command to server to remove the course in the DB
     * @param course_id the course whose id is this variable will be removed
     */
    public static void sendCommandRemoveCourse(int course_id) throws IOException {
        String command = "RemoveCourse";
        out.writeObject(command);
        out.writeInt(course_id);
        out.flush();
    }
    
    public static Question sendCommandCreateQuestion(String title, String body, int type, int course_id, int user_id) throws IOException, ClassNotFoundException{
        String command = "CreateQuestion";
        out.writeObject(command);
        out.writeObject(title);
        out.writeObject(body);
        out.writeInt(type);
        out.writeInt(course_id);
        out.writeInt(user_id);
        out.flush();
        return (Question)in.readObject();
    }

    /**
     * 
     * @param frame 
     */
    public static void createCourseButtonClicked(MainFrame frame) {
        CourseEditDialog courseEditDialog = new CourseEditDialog(frame, true, "newCourse", "", CourseEditDialog.CREATE_FRAME);
        int returnOption = courseEditDialog.getReturnOption();
        int course_id=-1;
        if (returnOption == CourseEditDialog.OK_OPTION) {
            try {
                course_id=sendCommandCreateCourse(UserProfile.user_id, courseEditDialog.getTitle(), courseEditDialog.getBody());
            } catch (IOException ex) {
                Logger.getLogger(FunctionLibrary.class.getName()).log(Level.SEVERE, null, ex);
            }
            if(course_id!=-1){
                //add course successfully now update courseList and courseListModel
                Course newCourse=new Course(course_id,courseEditDialog.getTitle(),courseEditDialog.getBody());
                
                // add a new course in the list and make it selected
                courseList.add(newCourse);
                courseListModel.addElement(newCourse.getTitle());
                frame.getCourseSelectList().setSelectedIndex(courseListModel.size()-1);
                frame.getCourseSelectList().ensureIndexIsVisible(courseListModel.size()-1);
            }else{
                // failed to create
            }
            

        }
        courseEditDialog.dispose();
    }

    /**
     * 
     * @param frame 
     */
    public static void editCourseButtonClicked(MainFrame frame) {
        int index = frame.getCourseSelectList().getSelectedIndex();

        //should check here whether the selection is valid

        // get the info of selected course
        int edit_course_id = -1;
        String title = "";
        String body = "";
        edit_course_id = courseList.get(index).getCourse_id();
        title = courseList.get(index).getTitle();
        body = courseList.get(index).getBody();

        if (edit_course_id == -1) {
            return;
        }

        CourseEditDialog courseEditDialog = new CourseEditDialog(frame, true, title, body, CourseEditDialog.EDIT_FRAME);
        int returnOption = courseEditDialog.getReturnOption();

        if (returnOption == CourseEditDialog.OK_OPTION) {// if user confrimed
            try {
                sendCommandEditCourse(edit_course_id, courseEditDialog.getTitle(), courseEditDialog.getBody());
            } catch (IOException ex) {
                Logger.getLogger(FunctionLibrary.class.getName()).log(Level.SEVERE, null, ex);
            }

            Course courseAfterEdit = new Course(edit_course_id, courseEditDialog.getTitle(), courseEditDialog.getBody());

            // update the arrayList
            courseList.set(index, courseAfterEdit);

            // update the elements in listModel, makes it visible and selected
            courseListModel.setElementAt(courseAfterEdit.getTitle(), index);
            frame.getCourseSelectList().setSelectedIndex(index);
            frame.getCourseSelectList().ensureIndexIsVisible(index);
            Logger.getLogger(Logger.GLOBAL_LOGGER_NAME).info(courseList.size() + "\n");

            // print out the arrayList to check
            for (Course c : courseList) {
                Logger.getLogger(Logger.GLOBAL_LOGGER_NAME).info(c.getTitle());
            }
        }
        courseEditDialog.dispose();
    }

    /**
     * pre: this function is called after user clicked the remove button on the course list page
     * post: removes the selected course on the list and calls other function to send command to DB to delete the course
     * @param frame the frame where user operated
     */
    public static void removeCourseButtonClicked(MainFrame frame) {

        //should check whether the selection is valid
        int index = frame.getCourseSelectList().getSelectedIndex();

        //get course info
        int remove_course_id = -1;
        remove_course_id = courseList.get(index).getCourse_id();

        if (remove_course_id != -1) {
            int option = JOptionPane.showConfirmDialog(frame,
                    "You are going to permanently delete a course in your account. This action cannot be undo !\nAre you sure?",
                    "Delete Confirmation",
                    JOptionPane.OK_CANCEL_OPTION,
                    JOptionPane.WARNING_MESSAGE,
                    null);
            if (option != JOptionPane.OK_OPTION) {
                return;
            }
            try {
                sendCommandRemoveCourse(remove_course_id);
                courseListModel.remove(index);
                courseList.remove(index);
            } catch (IOException ex) {
                Logger.getLogger(FunctionLibrary.class.getName()).log(Level.SEVERE, null, ex);
            }
            int size = courseListModel.getSize();
            if (size == 0) {
                //nothing is left in the list
            } else {
                if (index == size) {
                    // removed item is in last position
                    index--;
                }
                frame.getCourseSelectList().setSelectedIndex(index);
                frame.getCourseSelectList().ensureIndexIsVisible(index);
            }
        }
    }

    public static void goToQuestionPage(MainFrame frame) {
        int index = frame.getCourseSelectList().getSelectedIndex();
        if (index == -1) {
            return;
        }
        frame.getCourseSelectPanel().setVisible(false);
        frame.getQuestionPanel().setVisible(true);
        selectedCourse_id = courseList.get(index).getCourse_id();
        // get questionList
        // make the text in title selected
    }

    public static void createAndSaveQuestion(MainFrame frame) {
        String title = frame.getQuicklyAddQuestionTitle().getText();
        Question question = null;
        try {
            question = sendCommandCreateQuestion(title, "", 1, selectedCourse_id, UserProfile.user_id);
        } catch (IOException ex) {
            Logger.getLogger(FunctionLibrary.class.getName()).log(Level.SEVERE, null, ex);
        } catch (ClassNotFoundException ex) {
            Logger.getLogger(FunctionLibrary.class.getName()).log(Level.SEVERE, null, ex);
        }
        // add the question to the list
    }

    public static String encoderByMd5(String str) throws NoSuchAlgorithmException, UnsupportedEncodingException{
        MessageDigest md5=MessageDigest.getInstance("MD5");
        BASE64Encoder base64en = new BASE64Encoder();
        String newstr=base64en.encode(md5.digest(str.getBytes("utf-8")));
        return newstr;
    }
    
    public static void conTest() {
    }
}
